﻿using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Configuration;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using XuanXiang.Infrastructure.Attr;
using XuanXiang.Infrastructure.Dto.Request;
using XuanXiang.Infrastructure.Dto.Request.Goods;
using XuanXiang.Infrastructure.Dto.Request.Login;
using XuanXiang.Infrastructure.Dto.Response;
using XuanXiang.Infrastructure.Dto.Response.Goods;
using XuanXiang.Infrastructure.EFCore.MySql;
using XuanXiang.Infrastructure.IOC;
using XuanXiang.Infrastructure.Tools;
using XuanXiang.Service.EFCore;
using XuanXiang.Service.Interface;
using static Microsoft.EntityFrameworkCore.DbLoggerCategory;

namespace XuanXiang.Service.Instance
{
    [Inject_]
    public class Goods_Service : Base_Service, I_Goods_Service
    {
        private readonly Goods_IOC _goods_IOC;
        private readonly Supplier_IOC _supplier_IOC;
        private readonly Merchant_IOC _merchant_IOC;
        private readonly Sys_IOC _sys_IOC;
        private readonly IConfiguration _configuration;

        public Goods_Service(Goods_IOC goods_IOC, 
            Sys_IOC sys_IOC, Supplier_IOC supplier_IOC,
            Merchant_IOC merchant_IOC,
            IConfiguration configuration)
        {
            _goods_IOC = goods_IOC;
            _supplier_IOC = supplier_IOC;
            _merchant_IOC = merchant_IOC;
            _sys_IOC = sys_IOC;
            _configuration = configuration;
        }

        /// <summary>
        /// 新增商品
        /// </summary>
        /// <param name="dto"></param>
        /// <returns></returns>
        /// <exception cref="NotImplementedException"></exception>
        public Api_Result_Dto Add_Goods(GoodsAdd_Dto dto)
        {
            Good goods = new Good()
            {
                Gid = Config.GUID(),
                Gname = dto.name,
                Gbirthday = dto.birthday,
                Gcover = dto.img,
                GcreateTime = DateTime.Now,
                Gexpiryday = dto.expiryday,
                Gexplain = dto.explain,
                Ginventory = 0,
                GisBan = 0,
                GisPromote = 0,
                GisShelve = 0,
                Gloss = 0,
                Gprice = dto.price,
                GpromoteBegin = null,
                GpromoteEnd = null,
                GpromotePrice = 0,
                Gsales = 0,
                GSid = null,
                Gspecs = dto.specs,
                Gtype = dto.type
            };

            _goods_IOC._goods_EFCore.Add(goods);
            _goods_IOC._goods_EFCore.SaveChanges();
            return Get_Result(0, "新增成功");
        }

        /// <summary>
        /// 商品补货
        /// </summary>
        /// <param name="dto"></param>
        /// <returns></returns>
        /// <exception cref="NotImplementedException"></exception>
        public async Task<Api_Result_Dto> Add_Inventory(AddInventory_dto dto)
        {
            var data = await _goods_IOC._goods_EFCore.GetAll(d => d.Gid == dto.id).SingleOrDefaultAsync();
            data.Ginventory =(data.Ginventory + dto.count);
            _goods_IOC._goods_EFCore.Update(data);
            var result = await _goods_IOC._goods_EFCore.SaveChangesAsync();
            return Get_Result(result);

        }

        /// <summary>
        /// 商品删除
        /// </summary>
        /// <param name="dto"></param>
        /// <returns></returns>
        /// <exception cref="NotImplementedException"></exception>
        public async Task<Api_Result_Dto> Delete_Goods(Delete_Dto dto)
        {
            var goods = await _goods_IOC._goods_EFCore.GetAll(d => dto.ids!.Contains(d.Gid)).ToListAsync();
            _goods_IOC._goods_EFCore.DeleteRange(goods);
            var result = await _goods_IOC._goods_EFCore.SaveChangesAsync();
            return Get_Result(result);
        }

        /// <summary>
        /// 获取所有商品
        /// </summary>
        /// <param name="dto"></param>
        /// <returns></returns>
        /// <exception cref="NotImplementedException"></exception>
        public async Task<Api_Result_Dto> Get_Goods(Fenye_Dto dto)
        {
            int total = 0;
            var isAsc = dto.order == "ascending" ? true : false;
            IQueryable<Good> query;
            if (dto.isPrice)
            {
                query = _goods_IOC._goods_EFCore.GetAll<double?>(
                    out total,
                    dto.page,
                    dto.limit,
                    isAsc,
                    o => o.Gprice
                );
            }
            else
            {
                query = _goods_IOC._goods_EFCore.GetAll<int?>(
                    out total,
                    dto.page,
                    dto.limit,
                    isAsc,
                    o => o.Ginventory
                );
            }


            // 构建查询条件
            query = query.Where(d => d.Gname!.Contains(dto.key!));

            // 处理 isShelve 条件
            if (dto.isShelve != -1)
            {
                query = query.Where(d => d.GisShelve == dto.isShelve);
            }

            // 处理 isBan 条件
            if (dto.isBan != -1)
            {
                query = query.Where(d => d.GisBan == dto.isBan);
            }

            // 如果 isShelve 和 isBan 都为 -1，则忽略这两个条件
            // 否则已经添加了相应的条件

            var data = await query
                .Select(d => new Goods_Dto()
                {
                    id = d.Gid,
                    imgUrl = d.Gcover,
                    inventory = d.Ginventory,
                    isBan = d.GisBan == 1 ? true : false,
                    isShelve = d.GisShelve == 1 ? true : false,
                    name = d.Gname,
                    price = d.Gprice,
                    residueInventory = (d.Ginventory - d.Gsales),
                    sales = d.Gsales,
                    supplierName = null,
                    s_id = d.GSid,
                    tId = d.Gtype,
                    typeName = "", // 初始化为空字符串
                    time = d.GcreateTime!.Value.ToString("yyyy-MM-dd HH:mm:ss"),
                })
                .ToListAsync();

            /* // 获取所有商品类型ID
             var typeIds = data.Select(d => d.tId).Distinct().ToList();

             // 批量查询所有相关的字典类型
             var typeDictionary = await _sys_IOC._sys_Dictionary_EFCore
                 .GetAll(d => typeIds.Contains(d.Did))
                 .ToDictionaryAsync(d => d.Did, d => d.Dname);*/
            var types = _sys_IOC._sys_Dictionary_EFCore.GetAll().ToList();
            var supplier = _supplier_IOC._supplier_EFCore.GetAll().ToList();
            // 赋值typeName
            data.ForEach(d => {
                d.typeName = types.Where(c => c.Did == d.tId).Select(c => c.Dname).SingleOrDefault();
                d.supplierName = supplier.Where(c => c.Sid == d.s_id).Select(c => c.Sname).SingleOrDefault();
            });
            
            return Get_Result(0, "ok", new
            {
                data = data,
                total = total
            });
        }



        /// <summary>
        /// 获取商品类型列表
        /// </summary>
        /// <returns></returns>
        /// <exception cref="NotImplementedException"></exception>
        public async Task<Api_Result_Dto> Get_Goods_Type(Fenye_Dto dto)
        {
            var p_id = _configuration["Dictionary_Type:Goods"];
            var data = await _sys_IOC._sys_Dictionary_EFCore.GetAll(out int total,dto.page,dto.limit,false,o=>o.DcreateTime,
                d => d.DparentId == p_id && d.Dname.Contains(dto.key))
                .Select(d => new GoodsType_Dto()
                {
                    id = d.Did,
                    name = d.Dname,
                    parent_id = d.DparentId,
                    isBan = d.DisBan,
                    time=d.DcreateTime.Value.ToString("yyyy-MM-dd HH:mm:sss"),
                    s_id=d.Dsid
                }).ToListAsync();

            var supplier = _supplier_IOC._supplier_EFCore.GetAll().ToList();

            data.ForEach(d => {
                d.supplier = supplier.Where(c => c.Sid == d.s_id).Select(c => c.Sname).SingleOrDefault();
                d.goodsCount = _goods_IOC._goods_EFCore.GetAll(c => c.Gtype == d.id).Count();
            });

            return Get_Result(0, "ok", new { 
            data=data,
            total=total
            });

        }

        /// <summary>
        /// 获取单个商品详情
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        /// <exception cref="NotImplementedException"></exception>
        public async Task<Api_Result_Dto> Get_Single_Goods(string? id)
        {
            var data=await _goods_IOC._goods_EFCore.GetAll(d=>d.Gid == id)
                .Select(d => new GoodsDetails_Dto(){
                name=d.Gname,
                imgUrl=d.Gcover,
                price=d.Gprice,
                isShelve=d.GisShelve,
                isBan=d.GisBan,
                id=d.Gid,
                inventory=d.Ginventory,
                time=d.GcreateTime.Value.ToString("yyyy-MM-dd HH:mm:ss"),
                sales=d.Gsales,
                expiryday=d.Gexpiryday,
                s_id=d.GSid,
                tId=d.Gtype,
                specs=d.Gspecs,
                birthday=d.Gbirthday.Value.ToString("yyyy-MM-dd HH:mm:ss"),
                explain=d.Gexplain
                })
                .SingleOrDefaultAsync();
            //所有供应商
            var suppliers = _supplier_IOC._supplier_EFCore.GetAll(d=>d.Sid.Contains(data.s_id));
            if (suppliers.Any())
            {
                data.supplierName = suppliers.Select(d=>d.Sname).Single();
            }
            else {
                data.supplierName = null;
            }


            //所有类型
            var types = _sys_IOC._sys_Dictionary_EFCore.GetAll().ToList();

            data.typeName = types.Where(c => c.Did.Contains(data.tId)).Select(c => c.Dname).SingleOrDefault();

            return Get_Result(0, "ok", data);
        }

        /// <summary>
        /// 获取单个商品的销售数据
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        /// <exception cref="NotImplementedException"></exception>
        public async Task<Api_Result_Dto> Get_Single_Goods_SalesData(Fenye_Dto dto)
        {
            var data=await _merchant_IOC._order_Details_EFCore
                .GetAll(out int total,dto.page,dto.limit,false,o=>o.OdCreateTime,d=>d.OdGid==dto.id)
                .Select(d=>new Goods_SalesData_Dto() { 
                id=d.OdId,
                goodsName=d.OdName,
                isComplete=d.OdIsComplete,
                isReceive=d.OdIsReceive,
                isSend=d.OdIsSend,
                m_id=d.OdMid,
                s_id=d.OdSid,
                money=d.OdMoney,
                price=d.OdPrice,
                number=d.OdNumber,
                time=d.OdCreateTime!.Value.ToString("yyyy-MM-dd HH:mm:ss")
                }).ToListAsync();

            var supplier = _supplier_IOC._supplier_EFCore.GetAll().ToList();
            var merchant = _merchant_IOC._merchant_EFCore.GetAll().ToList();

            data.ForEach(d => {
                d.merchant = merchant.Where(c => c.MId == d.m_id).Select(c => c.MName).SingleOrDefault();
                d.supplier = supplier.Where(c => c.Sid == d.s_id).Select(c => c.Sname).SingleOrDefault();
            });

            return Get_Result(0, "ok", new
            {
                data = data,
                total=total
            }) ;
        }

        /// <summary>
        /// 修改商品的上架/下架
        /// </summary>
        /// <param name="dto"></param>
        /// <returns></returns>
        /// <exception cref="NotImplementedException"></exception>
        public async Task<Api_Result_Dto> Update_Shelve(Change_ShelveOrBan_dto dto)
        {
            var goods = await _goods_IOC._goods_EFCore.GetAll(d => d.Gid == dto.id).SingleOrDefaultAsync();
            goods!.GisShelve = dto.isShelve;
            goods.GisBan=dto.isBan;
            _goods_IOC._goods_EFCore.Update(goods);
           var result= await _goods_IOC._goods_EFCore.SaveChangesAsync();
            return Get_Result(result);
            
        }
    }
}
